package org.jeecg.modules.system.controller;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.dingtalk.api.response.OapiUserGetResponse;
import com.dingtalk.api.response.OapiUserGetuserinfoResponse;
import com.xkcoding.justauth.AuthRequestFactory;
import lombok.extern.slf4j.Slf4j;
import me.zhyd.oauth.model.AuthCallback;
import me.zhyd.oauth.model.AuthResponse;
import me.zhyd.oauth.request.AuthRequest;
import me.zhyd.oauth.utils.AuthStateUtils;
import org.jeecg.common.api.vo.Result;
import org.jeecg.common.constant.CommonConstant;
import org.jeecg.common.system.api.ISysBaseAPI;
import org.jeecg.common.system.util.JwtUtil;
import org.jeecg.common.util.PasswordUtil;
import org.jeecg.common.util.RedisUtil;
import org.jeecg.common.util.oConvertUtils;
import org.jeecg.config.Env;
import org.jeecg.modules.shiro.auth.AuthHelper;
import org.jeecg.modules.system.entity.SysUser;
import org.jeecg.modules.system.service.ISysUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;

import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;

/**
 * @Author scott
 * @since 2018-12-17
 */
@Controller
@RequestMapping("/dingTalkLogin")
@Slf4j
public class DingTalkLoginController {
	@Autowired
	private ISysUserService sysUserService;
	
	@Autowired
	private ISysBaseAPI sysBaseAPI;
	@Autowired
    private RedisUtil redisUtil;
	@Autowired
	private AuthRequestFactory factory;

	@RequestMapping("/{source}/{code}")
	@ResponseBody
    public Result<JSONObject> login(@PathVariable("source") String source,@PathVariable("code")String code) {
		log.info("钉钉免登录进入：" + source + "！");
		String accessToken = null;
		OapiUserGetuserinfoResponse response1;
		String userId = null;
		Result<JSONObject> result = new Result<JSONObject>();
		try {
			accessToken = AuthHelper.getAccessToken(Env.APP_KEY, Env.APP_SECRET);
			log.info("钉钉免登录获取token：" + accessToken );
			response1 = AuthHelper.getUserId(code, accessToken);
			userId = response1.getUserid();
			log.info("钉钉免登录获取userid：" + response1+"userId:"+userId );
			if (response1.getErrcode() != 0){
				result.setSuccess(false);
				log.info("钉钉免登录进入：" + source + "获取用户id失败！");
				result.setMessage("获取用户id失败");
				return result;
			}else {
				OapiUserGetResponse userInfo = AuthHelper.getUserInfo(accessToken, userId);
				if (!userInfo.isSuccess()){
					result.setMessage("获取钉钉用户失败！");
					result.setSuccess(false);
					return result;
				}
				log.info("钉钉免登录进入获取用户信息："+ userInfo);
				String name = userInfo.getName();
				String mobile = userInfo.getMobile();
				String avatar = userInfo.getAvatar();
				String nickname = userInfo.getNickname();
				log.info("钉钉免登录进入获取用户信息：name:"+name+"mobile"+mobile+"avatar"+avatar+"nickname"+nickname);
				//判断有没有这个人
				LambdaQueryWrapper<SysUser> query = new LambdaQueryWrapper<SysUser>();
				query.eq(SysUser::getThirdId, userId);
				query.eq(SysUser::getThirdType, source);
				List<SysUser> thridList = sysUserService.list(query);
				SysUser user = null;
				if(thridList==null || thridList.size()==0) {
					user = new SysUser();
					user.setActivitiSync(CommonConstant.ACT_SYNC_0);
					user.setDelFlag(CommonConstant.DEL_FLAG_0);
					user.setStatus(1);
					user.setThirdId(userId);
					user.setThirdType(source);
					user.setAvatar(avatar);
					user.setPhone(mobile);
					user.setUsername(userId);
					user.setRealname(name);
					//设置初始密码
					log.info("钉钉生产系统设置初始密码----------------");
					String salt = oConvertUtils.randomGen(8);
					log.info("钉钉生产系统设置初始密码生成salt:----------------"+salt);
					user.setSalt(salt);
					String passwordEncode = PasswordUtil.encrypt(user.getUsername(), "123456", salt);
					log.info("钉钉生产系统设置初始密码生成passwordEncode:----------------"+passwordEncode);
					user.setPassword(passwordEncode);
					sysUserService.saveThirdUser(user);
				}else {
					//已存在 只设置用户名 不设置头像
					user = thridList.get(0);
					//user.setUsername(username);
					//sysUserService.updateById(user);
				}
				// 生成token
				log.info("钉钉生产系统可用token!+显示密码：" + user.getPassword()+"----------------");
				String token = JwtUtil.sign(user.getUsername(), user.getPassword());
				log.info("钉钉生产系统可用token：" + token );
				redisUtil.set(CommonConstant.PREFIX_USER_TOKEN + token, token);
				// 设置超时时间
				redisUtil.expire(CommonConstant.PREFIX_USER_TOKEN + token, JwtUtil.EXPIRE_TIME / 1000);
				JSONObject obj = new JSONObject();
				//用户登录信息
				obj.put("userInfo", userInfo);
				//token 信息
				obj.put("token", token);
				result.setResult(obj);
				result.setSuccess(true);
				result.setCode(200);
				log.info("钉钉生产系统可用token：成功" + result );
				return  result;
			}
		} catch (Exception e) {
			e.printStackTrace();
			log.info("钉钉生产系统可用token：报异常" + e.getMessage() );
		}
		result.setSuccess(false);
		result.setMessage("钉钉登录异常,请联系管理员");
		return result;
    }
	
	@SuppressWarnings("unchecked")
	@RequestMapping(value = "/getLoginUser/{token}", method = RequestMethod.GET)
	@ResponseBody
	public Result<JSONObject> getLoginUser(@PathVariable("token") String token) throws Exception {
		Result<JSONObject> result = new Result<JSONObject>();
		String username = JwtUtil.getUsername(token);
		//1. 校验用户是否有效
		SysUser sysUser = sysUserService.getUserByName(username);
		result = sysUserService.checkUserIsEffective(sysUser);
		if(!result.isSuccess()) {
			return result;
		}
		JSONObject obj = new JSONObject();
		//用户登录信息
		obj.put("userInfo", sysUser);
		//token 信息
		obj.put("token", token);
		result.setResult(obj);
		result.setSuccess(true);
		result.setCode(200);
		sysBaseAPI.addLog("用户名: " + username + ",登录成功[钉钉免登录]！", CommonConstant.LOG_TYPE_1, null);
		return result;
	}
	
}